<template>
  <!-- 弹窗组件 抽离 -->
  <el-dialog :visible.sync="isShow" :title="title" @close="closeEvent">
    <el-form ref="form" label-width="120px" :model="form" :rules="rules">
      <el-form-item prop="name" label="部门名称">
        <el-input v-model.trim="form.name" />
      </el-form-item>
      <el-form-item prop="code" label="部门编码">
        <el-input v-model.trim="form.code" />
      </el-form-item>
      <el-form-item prop="manager" label="部门负责人">
        <el-select v-model.trim="form.manager" @focus="focusEvent">
          <el-option
            v-for="i in userList"
            :key="i.id"
            :label="i.username"
            :value="i.username"
          />
        </el-select>
      </el-form-item>
      <el-form-item prop="introduce" label="部门介绍">
        <el-input v-model.trim="form.introduce" />
      </el-form-item>
    </el-form>
    <template #footer>
      <div style="text-align: center">
        <el-button @click="closeEvent">取消</el-button>
        <el-button type="primary" @click="submit">确定</el-button>
      </div>
    </template>
  </el-dialog>
</template>

<script>
// 导入请求的函数
import {
  sysUserSimple,
  companyDepartmentPost,
  companyDepartmentPut
} from '@/api/departments.js'
export default {
  name: '',
  // 接收父组件传递的原始数据
  props: {
    initTreeData: {
      type: Array,
      // 默认值为空数组
      default: () => []
    }
  },
  data() {
    return {
      // 接收对话框的功能 添加add 编辑edit
      mode: 'add', // 默认为add
      // 接收当前点击项的数据
      itemData: [],
      // 默认不显示
      isShow: false,
      // 员工列表信息
      userList: [],
      // 获取表单的值 用户新增部门
      form: {
        name: '', //	string	非必须		部门名称，同级部门不可重复
        code: '', //	string	非必须		部门编码,所有编码不可重复
        introduce: '', //	string	非必须		介绍
        manager: '', // r	string	非必须		负责人名称
        pid: '' //	string	非必须		父级部门ID
      },
      rules: {
        //  点击项的数据 中有id,manager,name  原始数据中每一项都是一个数组,包含pid,name等
        // 部门名称添加时不能和同级部门重名  点击的添加是添加子集,则判断的是点击项的id与子集的pid

        // 当点击的是编辑功能时,名称部分是不可以与兄弟部门重名(兄弟的pid一致)并排除自己
        name: [
          { required: true, message: '必填', trigger: 'change' },
          {
            validator: (rule, value, callback) => {
              // 点击项的id值 存储在itemData中 与原始数据中的pid匹配
              // 从原始数据initTreeData中 itemData点击的那一项数据  过滤相等的值 放在一个数组中
              const tempArr = this.initTreeData.filter((item) => {
                if (this.mode === 'add') {
                  // 当是添加功能时,是添加子集,所以需要筛选出点击的id下所有子集,(点击项的id 是子集的统一pid)
                  return item.pid === this.itemData.id
                } else if (this.mode === 'edit') {
                  // 当是编辑功能时,是筛选出除了自己之外的兄弟部门(点击项的pid与其他原始数据的pid一致)
                  return (
                    // 筛选出 兄弟部门pid一致
                    item.pid === this.itemData.pid &&
                    // 且筛选出不是自己的id的  (自己的id是唯一的)
                    item.id !== this.itemData.id
                  )
                }
              })
              console.log(tempArr, '点击的id下的所有子集筛选后的新数组')
              // 验证重名
              const bol = tempArr.some((item) => {
                return item.name === value
              })
              bol ? callback(new Error(`部门名称重名: ${value}`)) : callback()
            },
            trigger: 'blur'
          }
        ],
        // 自定义校验规则时,触发的提示messgae,以及触发的条件可以不用写
        code: [
          { required: true, message: '必填', trigger: 'change' },
          // code不允许与任何一个重名
          {
            validator: (rule, value, callback) => {
              // value与原始数据中的code相比较 返回布尔值
              const bol = this.initTreeData.some((item) => {
                if (this.mode === 'add') {
                  // 当是添加功能时,如果输入的值只要有一项与原始数据中的code一致,表示重名,返回true
                  return item.code === value
                } else if (this.mode === 'edit') {
                  // 如果是编辑功能,则需要判断值是否与原始的值(传入的原始数据数组中的每一项对象中的的id)一致且不是自己的code(点击项的id) 进行校验
                  return item.code === value && item.id !== this.itemData.id
                }
              })
              bol ? callback(new Error(`部门编码重名: ${value}`)) : callback()
            }
          }
        ],
        manager: [{ required: true, message: '必填', trigger: 'change' }],
        introduce: [{ required: true, message: '必填', trigger: 'change' }]
      }
    }
  },
  computed: {
    // 不同的场景,显示不同的标题
    title() {
      // 适用于多种状态下的标题obj[变量名]
      return { add: '新增部门', edit: '编辑部门' }[this.mode]
    }
  },
  watch: {
    isShow(newVal) {
      if (!newVal) {
        // 重置表单验证与值(重置为第一次渲染时的样子,但是如果第一次渲染时为编辑的,会导致后面的每次重置会重置为第一次编辑的表单内数据,为规避需要强行重置表单为空)
        this.$refs.form.resetFields()
        // 重置表单内容
        this.form = {
          name: '',
          code: '',
          introduce: '',
          manager: '',
          pid: ''
        }
      }
    }
  },
  mounted() {
    // 监听事件总线
    this.$bus.$on('showDialog', (bol, item, mode) => {
      this.isShow = bol
      // 将传递的点击项数据赋值
      this.itemData = item
      // 将点击项的id 赋值给子项的pid
      this.form.pid = item.id
      // 将用户点击后 需要实现的功能传递
      this.mode = mode
      // 如果是编辑功能,需要回显数据,把点击项的数据 深拷贝给form进行显示 回显数据
      if (mode === 'edit') {
        this.form = JSON.parse(JSON.stringify(item))
      }
      // 点击项的数据 中有id,manager,name
      console.log(this.itemData, '点击项的数据')
    })
  },
  // 销毁
  beforeDestroy() {
    this.$bus.$off('showDialog')
  },
  created() {},
  methods: {
    // 点击取消
    closeEvent() {
      this.isShow = false
      // 利用监听属性 监听表单数据变化
      // 重置表单验证与值(重置为第一次渲染时的样子,但是如果第一次渲染时为编辑的,会导致后面的每次重置会重置为第一次编辑的表单内数据,为规避需要强行重置表单为空)
      // this.$refs.form.resetFields()
      // // 重置表单内容
      // this.form = {
      //   name: '',
      //   code: '',
      //   introduce: '',
      //   manager: '',
      //   pid: ''
      // }
    },
    // 当 input 获得焦点时触发 获取员工简单列表
    async focusEvent() {
      if (this.userList.length === 0) {
        const res = await sysUserSimple()
        console.log(res, '获取员工简单列表')

        this.userList = res.data
      }
    },
    // 点击确定
    submit() {
      this.$refs.form.validate(async(result) => {
        if (result) {
          // 预校验通过 调用接口 完成新增/编辑
          if (this.mode === 'add') {
            // 新增的接口
            await companyDepartmentPost(this.form)
            // 提示新增成功
            this.$message.success('新增部门成功')
          } else if (this.mode === 'edit') {
            // 编辑的接口
            await companyDepartmentPut(this.form)
            // 提示修改成功
            this.$message.success('修改成功')
          }
          // 关闭弹框
          this.isShow = false
          // 刷新父级列表的数据 通过子传父 触发父级的调用接口刷新页面改变
          this.$emit('getData')
          // 在关闭弹框的时候弹框的close事件 清空表单数据 与点击取消触发事件一致
        }
      })
    }
  }
}
</script>
<style lang="less" scoped></style>
